//
//  MDHRouter.m
//  JSTech
//
//  Created by 高得华 on 2019/4/27.
//  Copyright © 2020 华&梅. All rights reserved.
//

#import "MDHRouter.h"
#import <pthread/pthread.h>
#import "MDHMacroHeader.h"

@interface MDHRouter ()

/// viewModel到viewController的映射
@property (nonatomic, copy) NSDictionary *viewModelViewMappings;
/// APP的网络服务层
@property (nonatomic, readwrite, strong) MDHViewModelServicesImpl * services;
/// APP管理的导航栏的堆栈
@property (nonatomic, readwrite, strong) MDHNavigationControllerStack *navigationControllerStack;

///


@end

@implementation MDHRouter

static MDHRouter *sharedInstance_ = nil;

+ (id)allocWithZone:(struct _NSZone *)zone
{
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance_ = [super allocWithZone:zone];
    });
    return sharedInstance_;
}

- (id)copyWithZone:(NSZone *)zone
{
    return sharedInstance_;
}

+ (instancetype)sharedInstance {
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance_ = [[self alloc] init];
    });
    return sharedInstance_;
}

- (instancetype)init
{
    self = [super init];
    if (self) {
        // Config Service
        self.services = [[MDHViewModelServicesImpl alloc] init];
        // Config Nav Stack
        self.navigationControllerStack = [[MDHNavigationControllerStack alloc] initWithServices:self.services];
        self.viewModelViewMappings = @{};
    }
    return self;
}

- (MDHViewController *)viewControllerForViewModel:(MDHViewModel *)viewModel {
    NSString * cbn = [[[NSBundle mainBundle] infoDictionary][@"CFBundleName"] stringByAppendingString:@"."];
    NSString * vm = NSStringFromClass(viewModel.class);
    if ([vm hasPrefix:cbn]) {
        vm = [vm substringFromIndex:cbn.length];
    }
    NSString *viewController = @"";
    if (self.viewModelViewMappings.count > 0) {
        viewController = self.viewModelViewMappings[vm];
    }
    if (viewController.length <= 0) {
        DTLog(@"- ==%@对应的viewController:为空",vm);
        return [MDHViewController new];
    }
    
    Class class = NSClassFromString(viewController);
    if (class == nil) {
        class = NSClassFromString([cbn stringByAppendingString:viewController]);
    }
    
    NSParameterAssert([class isSubclassOfClass:[MDHViewController class]]);
    NSParameterAssert([class instancesRespondToSelector:@selector(initWithViewModel:)]);
    //[self studayDxc];
    MDHViewController * vc = [[class alloc] initWithViewModel:viewModel];
    viewModel.view = vc.view;
    return vc;
}

/// Retrieves the view corresponding to the given view model.
///
/// viewModel - The view model
///
/// Returns the view corresponding to the given view model.
- (NSString *)viewModelForViewController:(MDHViewController *)viewController {
    NSString * cbn = [[[NSBundle mainBundle] infoDictionary][@"CFBundleName"] stringByAppendingString:@"."];
    NSString * vm = NSStringFromClass(viewController.class);
    if ([vm hasPrefix:cbn]) {
        vm = [vm substringFromIndex:cbn.length];
    }
    NSString *viewModel = @"MDHViewModel";
    if (self.viewModelViewMappings.count > 0) {
        viewModel = self.viewModelViewMappings[vm];
    }
    if (viewModel.length <= 0) {
        DTLog(@"- ==%@对应的MDHViewModel:为空",vm);
    }
    return viewModel;
}


/// 这里是viewModel -> ViewController的映射
/// If You Use Push 、 Present 、 ResetRootViewController ,You Must Config This Dict
- (void)viewModelViewMappings:(NSDictionary *)dict {
    NSMutableDictionary * dict1 = @{
    /// - ==== Tabbar H5 其他 ===== -
    @"MDHWebViewModel":@"MDHWKWebViewController",///H5页面
    @"MDHSegmentedControlViewModel":@"MDHHtTitleViewController",//Segment
    @"MMEditTextViewModel": @"MMEditTextViewController",///输入文本视图
    }.mutableCopy;
    if (dict) {
        [dict1 addEntriesFromDictionary:dict];
    }
    self.viewModelViewMappings = dict1.copy;
}

/*
/// 这里是viewModel -> ViewController的映射
/// If You Use Push 、 Present 、 ResetRootViewController ,You Must Config This Dict
*/

///多线程的学习
- (void)studayDxc {
    ///学习新函数或者方法的三要素
    ///1.函数的功能
    ///2.函数的参数
    ///3.函数的返回值
    //MARK: pthread
    ///创建多线程 C语言中的
    ///第一个参数 线程编号的指针
    ///第二个参数 线程的属性 nil(oc中的空对象) NULL C语言空指针
    ///第三个参数 void * (*) (void *) void *指向任何类型的指针 类似于OC中的 id
    ///第四个参数 要执行函数的参数
    
    ///函数的返回值 int 0代表成功 1代表失败
    pthread_t pthread;//线程编号
    int result = pthread_create(&pthread, NULL, demo, NULL);
    if (result == 0) {
        NSLog(@"线程创建成功");
    }else{
        NSLog(@"线程创建失败");
    }
    
    
    //MARK: - == NSThread
    ///1.无参数
    ///方法一:
    NSThread * thread = [[NSThread alloc] initWithTarget:self selector:@selector(demoNSThread1) object:nil];
    [thread start];
    ///方法二:
    [NSThread detachNewThreadSelector:@selector(demoNSThread1) toTarget:self withObject:nil];
    ///方法三:
    [self performSelectorInBackground:@selector(demoNSThread1) withObject:nil];
    
    ///带参数
    ///方法四
    NSThread * thread1 = [[NSThread alloc] initWithTarget:self selector:@selector(demoNSThread2:) object:@"参数"];
    [thread1 start];
}

///函数
void *demo(void *param) {
    NSLog(@"测试线程pthread, %@", [NSThread currentThread]);
    return NULL;
}

///demo1 NSThread
- (void)demoNSThread1 {
    NSLog(@"当前线程:%@",[NSThread currentThread]);
}

- (void)demoNSThread2:(NSString *)param {
    NSLog(@"当前线程:%@, 参数:%@",[NSThread currentThread], param);
}

@end
